using System;
using System.Collections.Generic;
using System.Text;
using OpenComposite.Base.Designer;
using System.Drawing;
using System.Xml;
using System.Xml.Schema;
using OpenComposite.EII.Designer.Generic;

namespace OpenComposite.EII.Designer.BRules
{
	public class THENELSESymbol : Symbol, IConnector, IConnectorFactory
	{
		#region Initialization
		public THENELSESymbol()
		{
			init();
		}
		private void init()
		{
			this.BeginUpdate();

			//this.Name = "thenelseSymbol" + GetCount(typeof(THENELSESymbol));
			this.Text = "Then-Else";
			this.NameTextBox.Visible = false;

			this.Border = BorderType.Rectangle;
			this.BorderColor = Color.DarkBlue;
			this.BorderWidth = 2;

			this.Size = new Size(120, 150);

			Rectangle rclient = this.CalculateClientArea();
			//
			// _thenAction
			//
			_thenAction = new ActionSymbol();
			_thenAction.Text = "THEN";
			_thenAction.ResultString = "";
			_thenAction.Bounds = new Rectangle(0, 0, rclient.Width, (int)( rclient.Height / 2 ) - 6);

			//
			// _elseAction
			//
			_elseAction = new ActionSymbol();
			_elseAction.Text = "ELSE";
			_elseAction.ResultString = "";
			_elseAction.Bounds = new Rectangle(0, (int)( rclient.Height / 2 ) + 2,
				rclient.Width, (int)( rclient.Height / 2 ) - 2);

			this.Controls.Add(_thenAction);
			this.Controls.Add(_elseAction);

			this.EndUpdate();
		}
		#endregion

		#region Public Members

		#region Properties

		public string ThenResultString
		{
			get { return _thenAction.ResultString; }
			set { _thenAction.ResultString = value; }
		}
		public string ElseResultString
		{
			get { return _elseAction.ResultString; }
			set { _elseAction.ResultString = value; }
		}
		#endregion

		#region Override

		#region Properties
		public override bool CanFocused
		{
			get
			{
				return true;
			}
		}
		public override bool CanMove
		{
			get
			{
				return false;
			}
		}
		public override bool CanResize
		{
			get
			{
				return true;
			}
		}
		public override ResizeSides ResizableSides
		{
			get
			{
				return ResizeSides.Left;
			}
		}
		public override bool CanSelect
		{
			get
			{
				return true;
			}
		}
		public override bool IsContainer
		{
			get
			{
				return false;
			}
		}
		public override bool NoClip
		{
			get
			{
				return false;
			}
		}
		public override bool UseGrid
		{
			get
			{
				return false;
			}
		}
		#endregion

		#region Drag&Drop
		public override void DropObject(object obj, Point location, System.Windows.Forms.MouseButtons button)
		{
			if ( this.IsDropAllowed(obj, location, button) && button == System.Windows.Forms.MouseButtons.Right ) {
				this.DesignerViewControl.AddRoute((DesignerControl)obj, this);
			}
		}
		public override bool IsDropAllowed(object obj, Point location, System.Windows.Forms.MouseButtons button)
		{
			return ( obj is IFSymbol || obj is ANDSymbol || obj is ORSymbol );
		}
		#endregion

		#region Paint
		public override void PaintBackground(System.Windows.Forms.PaintEventArgs pe)
		{
			base.PaintBackground(pe);
			Rectangle rect = this.GetPaintBounds();
			int y = rect.Top + (int)( rect.Height / 2 );
			pe.Graphics.DrawLine(Pens.Blue, rect.Left, y, rect.Right, y);
		}
		#endregion

		#endregion

		#endregion

		#region Protected Members

		#region Override
		protected override void OnSizeChanged(EventArgs e)
		{
			this.BeginUpdate();
			
			Rectangle rect = this.CalculateClientArea();
			if ( _thenAction != null )
				_thenAction.Size = new Size(rect.Width, ( rect.Height / 2 ) - 6);
			if ( _elseAction != null )
				_elseAction.Bounds = new Rectangle(0, ( rect.Height / 2 ) + 2, rect.Width, ( rect.Height / 2 ) - 2);

			this.EndUpdate();
			base.OnSizeChanged(e);
		}
		protected override void OnRemoved(EventArgs e)
		{
			DesignerControl[] successorsTHEN = _thenAction.GetSuccessors();
			DesignerControl[] successorsELSE = _elseAction.GetSuccessors();

			if ( successorsTHEN != null && successorsTHEN.Length > 0 ) {
				clearIFConditions(successorsTHEN);
			}
			if ( successorsELSE != null && successorsELSE.Length > 0 ) {
				clearIFConditions(successorsELSE);
			}
			_thenAction.Remove();
			_elseAction.Remove();
			base.OnRemoved(e);
		}

		private void clearIFConditions(DesignerControl[] successors)
		{
			foreach ( DesignerControl dc in successors ) {
				IFSymbol ifSym = dc as IFSymbol;
				if ( ifSym != null ) {
					ifSym.IFCondition = new IFSymbol.Condition(ifSym);
					ifSym.Refresh();
				}
			}
		}
		protected override void OnVisibleChanged()
		{
			// do nothing
		}
		#endregion

		#endregion

		#region Private Members

		#region Variables
		private ActionSymbol _thenAction;
		private ActionSymbol _elseAction;
		#endregion

		#region Methods
		#endregion

		#region Event Handlers
		#endregion

		#endregion

		#region IConnector Members

		public Point GetRouteEnd(RouteDockDirection dock)
		{
			Rectangle bounds = this.GetPaintBounds();
			return new Point(bounds.Left, bounds.Top + (int)( bounds.Height / 2 ));
		}

		public Point GetRouteStart(RouteDockDirection dock)
		{
			return Point.Empty;
		}

		#endregion

		#region IConnectorFactory Members

		public override bool CreateRouteEnd(DesignerControl controlStart,
			out IConnector connector, out System.Drawing.Drawing2D.LineCap cap,
			out System.Drawing.Drawing2D.CustomLineCap customcap, out RouteDockDirection dockStart,
			out RouteDockDirection dockEnd, out bool useEndConnectorAsRouteEnd)
		{
			bool bOK = base.CreateRouteEnd(controlStart,
				out connector, out cap, out customcap, out dockStart, out dockEnd, out useEndConnectorAsRouteEnd);

			dockEnd = RouteDockDirection.Left;

			return bOK;
		}

		public override bool CreateRouteStart(DesignerControl controlEnd,
			out IConnector connector, out System.Drawing.Drawing2D.LineCap cap,
			out System.Drawing.Drawing2D.CustomLineCap customcap, out RouteDockDirection dockStart,
			out RouteDockDirection dockEnd, out bool useStartConnectorAsRouteStart)
		{
			connector = null;
			cap = System.Drawing.Drawing2D.LineCap.Flat;
			customcap = null;
			dockStart = RouteDockDirection.Right;
			dockEnd = RouteDockDirection.Left;
			useStartConnectorAsRouteStart = false;

			return false;
		}

		#endregion

		#region IXmlSerializable Members

		public override XmlSchema GetSchema()
		{
			return null;
		}

		public override void ReadXml(XmlReader reader)
		{
			while ( reader.Read() ) {
				switch ( reader.Name ) {
					case "DesignerControl":
						if ( reader.NodeType == XmlNodeType.EndElement )
							return;
						break;
					case "THEN":
						this._thenAction.SetIdentifier(new Guid(reader.GetAttribute("ID")));
						this.ThenResultString = reader.ReadString();
						break;
					case "ELSE":
						this._elseAction.SetIdentifier(new Guid(reader.GetAttribute("ID")));
						this.ElseResultString = reader.ReadString();
						break;
					default:
						ReadStandardProperties(reader);
						break;
				}
			}
		}

		public override void WriteXml(XmlWriter writer)
		{
			WriteStandardProperties(writer);

			// Start THEN
			writer.WriteStartElement("THEN");
			writer.WriteAttributeString("ID", this._thenAction.Identifier.ToString());
			writer.WriteString(this.ThenResultString);
			writer.WriteEndElement();
			// End THEN

			// Start ELSE
			writer.WriteStartElement("ELSE");
			writer.WriteAttributeString("ID", this._elseAction.Identifier.ToString());
			writer.WriteString(this.ElseResultString);
			writer.WriteEndElement();
			// End ELSE
		}

		#endregion
	}
}
